package com.mlnx.bluwifi.sampleTool;

import com.alibaba.fastjson.JSONObject;
import com.mlnx.bluwifi.pojo.dto.SampleEntity;

import java.io.*;
import java.net.URL;
import java.net.URLConnection;

/**
 * @author zzb
 * 计算最大最小值
 * @create 2020/3/10 10:43
 */
public class Jisuan {
    public static void main(String[] args) {

        InputStream in = null;
        try {
            System.out.println("ap mac:{} 开始接收蓝牙数据");
            URL url = new URL("http://192.168.1.89/gap/rssi?rssi_interval=100");
            URLConnection connection = url.openConnection();
            connection.setReadTimeout(5000);
            in = connection.getInputStream();  //带资源的try-catch语句。自动关闭
            InputStream buffer = new BufferedInputStream(in);

            //将InputStream串链到一个Reader
            Reader reader = new InputStreamReader(buffer);
            BufferedReader bufferedReader = new BufferedReader(reader);
            String str = "";
            Long time = System.currentTimeMillis();

            int i = 0;
            int[] arr1 = new int[10];
            while (true) {
                str = bufferedReader.readLine();
                if (!((":keep-alive").equals(str) || str.length() == 0)) {
                    String spoValue = str.substring(5);
                    SampleEntity sampleEntity = JSONObject.parseObject(spoValue, SampleEntity.class);

                    arr1[i] = sampleEntity.getRssi();
//                    System.out.println(i+":"+sampleEntity.getRssi());
                    i++;
                    if (i == 10) {
//                        System.out.println("arr1的size"+arr1.length);
                        Jisuan jisuan = new Jisuan();
                        jisuan.find_pv(arr1, arr1.length);
                        i = 0;
                        arr1 = new int[10];
                    }

                    if ((System.currentTimeMillis() - time) > 10000) {

                    }
                }
            }
        } catch (Exception e) {
            if (!("Connection timed out: connect".equals(e.getMessage()) || "Read timed out".equals(e.getMessage()))) {

            }

        } finally {
            if (in != null) {
                try {
                    in.close();

                } catch (IOException e) {

                }
            }
        }

    }

    private static int BUF_SIZE = 10;
    private static int[] global_buf = new int[BUF_SIZE];
    private static int index = 0;

    private static int max_value = 0;
    private static int min_value = 0;

    private static int max_index = 0;
    private static int min_index = 0;
    private static int find_max_flag = 1;
    private static int find_min_flag = 0;
    private static int MIN_DIFFERENCE = 2;
    private static int MAX_DIFFERENCE = 7;
    private static int Threshold_Differ = 3;
    //差值平均数
    private static int avg_differ = 3;

    //快速排序算法(从小到大)
//arr:需要排序的数组，begin:需要排序的区间左边界，end:需要排序的区间的右边界
    void quickSort(int[] arr, int begin, int end) {

        //如果区间不只一个数
        if (begin < end) {
            int temp = arr[begin]; //将区间的第一个数作为基准数
            int i = begin; //从左到右进行查找时的“指针”，指示当前左位置
            int j = end; //从右到左进行查找时的“指针”，指示当前右位置
            //不重复遍历
            while (i < j) {
                //当右边的数大于基准数时，略过，继续向左查找
                //不满足条件时跳出循环，此时的j对应的元素是小于基准元素的
                while (i < j && arr[j] > temp) {
                    j--;
                }

                //将右边小于等于基准元素的数填入右边相应位置
                arr[i] = arr[j];
                //当左边的数小于等于基准数时，略过，继续向右查找
                //(重复的基准元素集合到左区间)
                //不满足条件时跳出循环，此时的i对应的元素是大于等于基准元素的
                while (i < j && arr[i] <= temp) {
                    i++;
                }
                //将左边大于基准元素的数填入左边相应位置
                arr[j] = arr[i];
            }


            //将基准元素填入相应位置
            arr[i] = temp;
            //此时的i即为基准元素的位置
            //对基准元素的左边子区间进行相似的快速排序
            quickSort(arr, begin, i - 1);
            //对基准元素的右边子区间进行相似的快速排序
            quickSort(arr, i + 1, end);
        }
        //如果区间只有一个数，则返回
        else {
            return;
        }
    }


    int find_pv(int[] buffer, int length) {

        if (length < 4) {
            return 0;
        }
//        for (int j = 0; j < length - 1; j++) {
//            System.out.print((buffer[j] + " "));
//        }
        int i = 0;
        quickSort(buffer, 0, length - 1);


        int tempdata = 0;
        //分别去掉最大的两个数以及最小的两个数，剩下的做算数平均
        for (i = 2; i < (length - 2); i++) {
            tempdata += buffer[i];
        }
        tempdata /= (length - 4);
        //第一个值
        if (index == 0 && global_buf[index] == 0) {
            global_buf[index] = tempdata;
            max_value = -100;
            min_value = -30;
        } else {
            //做加权平均
            global_buf[index] = (global_buf[(index + BUF_SIZE- 1) % BUF_SIZE] + 2 * tempdata) / 3;
            //与前一个数做差值
            int differ = Math.abs(global_buf[index] - global_buf[(index + BUF_SIZE - 1) % BUF_SIZE]);
            if(differ >= avg_differ + Threshold_Differ){
                //再次做平滑处理
                global_buf[index] = (global_buf[(index + BUF_SIZE - 1) % BUF_SIZE] + global_buf[index]) / 2;
                differ = Math.abs(global_buf[index] - global_buf[(index + BUF_SIZE - 1) % BUF_SIZE]);
                System.out.println(( differ));
            }
            if(find_max_flag==0){
                //最大值
                if(global_buf[index] > max_value){
                    max_value = global_buf[index];
                    max_index = index;
                    System.out.println("max_value="+ max_value);
                }

                //有两个连续变小的值并且最大值一直没有更新
                if(index >= (max_index + 2) % BUF_SIZE){
                    if(global_buf[index] + MIN_DIFFERENCE < global_buf[(index + BUF_SIZE - 1) % BUF_SIZE]
                            && global_buf[(index + BUF_SIZE - 1) % BUF_SIZE] + MIN_DIFFERENCE < max_value){
                        System.out.println("find the max");
                        find_max_flag = 1;
                        //标志位置0，开始找最小值
                        find_min_flag = 0;
                        min_value = max_value;
                        min_index = max_index;
                    }
                }
            }

            if(find_min_flag== 0){
                //最小值
                if(global_buf[index] < min_value){
                    min_value = global_buf[index];
                    min_index = index;
                    System.out.println("min_value ="+ min_value);
                }
                //有两个连续变大的值并且最小值一直没有更新
                if(index >= (min_index + 2) % BUF_SIZE){
                    if(global_buf[index] > global_buf[(index + BUF_SIZE - 1) % BUF_SIZE] + MIN_DIFFERENCE
                            && global_buf[(index + BUF_SIZE - 1) % BUF_SIZE] > min_value + MIN_DIFFERENCE){
                        System.out.println("=========find the min==========\r\n");
                        find_min_flag = 1;
                        //标志位置0，开始找最大值
                        find_max_flag = 0;
                        max_value = min_value;
                        max_index = min_index;
                    }
                }
            }
            avg_differ = (avg_differ + differ) / 2;
            //将差值平均数控制在一定范围内
            if(avg_differ < MIN_DIFFERENCE){
                avg_differ = MIN_DIFFERENCE;
            }else if(avg_differ > MAX_DIFFERENCE){
                avg_differ = MAX_DIFFERENCE;
            }


            System.out.println("avg_differ = "+ avg_differ);
        }
        System.out.println("global_buf[index] = "+ global_buf[index]);
        index = (index + 1 >= BUF_SIZE)? 0 : (index + 1);

        return tempdata;
    }


}
